home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
FM Towns: Free Software Collection 4
/
FM Towns Free Software Collection 4 - Disc 1.iso
/
t_os
/
magl
/
mag.c
< prev
next >
Wrap
C/C++ Source or Header
|
1991-10-18
|
11KB
|
450 lines
/*
* MAG & MAKI Library 'Mag.c' for FM-TOWNS
*
* - MAKIchan Graphic loader is not 鮪だ! -
*
* programmed by MALOR
*/
#include <egb.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "wild.h"
#include "mag.h"
#include "pixel.h"
#define tolower(x) (((x)<='Z')&&((x)>='A')?((x)-'A'+'a'):(x))
/* Global Vari. */
MAGHEADER maghead; /* MAGのヘッダ */
MKIHEADER mkihead; /* MAKIのベッダ */
int sizp; /* MAKIのピクセルサイズ */
int siza; /* MAGのflag aのサイズ */
int headtop; /* MAGのヘッダのオフセット */
char pal[768]; /* 現在のパレット情報 */
char *flga,*flgb,*flg,*pix; /* flag&pixel格納アドレス */
int xpixel; /* 横方向のピクセル数の半分 */
/* 現在メモリに存在するイメージ情報 */
char *vram=NULL; /* イメージ格納アドレス */
int screen_mode; /* スクリーンモード(MAG互換) */
int image_mode; /* メモリ上のデータのモード */
int lx,ly; /* 左上座標 */
int rx,ry; /* 右下座標 */
char comment[81]; /* コメント */
/* Prototype declaration */
int stringcmp(char *s,char *d);
void flag_write(void);
/* Main program */
void flag_write(void)
{
FILE *fp;
fp=fopen("flagdump","wb");
fwrite(flg,1,siza*8,fp);
fclose(fp);
}
int stringcmp(char *s,char *d)
{
for (;*s!='\0';s++,d++)
if ((tolower(*s))!=(tolower(*d)))
return FALSE;
return TRUE;
}
int mag_get_head(FILE *fp)
{
char buf[10],*p;
int i;
fseek(fp,0,0);
fread(buf,1,8,fp);
if (!stringcmp("MAKI02",buf))
return FALSE;
fseek(fp,0,0);
for(i=0,p=comment,headtop=0;;i++,headtop++) {
if (fread(buf,1,1,fp)!=1)
return FALSE;
if (*buf==EOC) {
*p = '\0';
headtop++;
break;
}
if (*buf==0x0d||*buf==0x0a)
i = 80;
if (i<80)
*p++ = *buf;
}
if (fread((char *)&maghead,1,sizeof(MAGHEADER),fp)<sizeof(MAGHEADER))
return FALSE;
/* flag a size */
xpixel = (maghead.screen&COL256)?(maghead.rx/4-maghead.lx/4+1)
:(maghead.rx/8-maghead.lx/8+1);
siza = (xpixel*(maghead.ry-maghead.ly+1)+7) / 8;
/*
printf(
"---------------------------------------------------------\n"
"ヘッダ情報\n"
"機種コード : %d 機種依存フラグ : %d 画面モード : %d\n"
"位置 : (%3d,%3d)-(%3d,%3d)\n"
"---------------------------------------------------------\n"
" | offset | size\n"
"---------------------------------------------------------\n"
"comment | 0 | %5d \n"
"header | %5d | 32 \n"
"palette | %5d | %5d \n"
"flag a | %5d | %5d \n"
"flag b | %5d | %5d \n"
"pixcel | %5d | %5d \n"
"---------------------------------------------------------\n\n"
,maghead.machine,maghead.rflg,maghead.screen
,maghead.lx,maghead.ly,maghead.rx,maghead.ry
,headtop,headtop,(headtop+32),(maghead.screen&COL256)?768:48
,headtop+maghead.offa,siza
,headtop+maghead.offb,maghead.sizb
,headtop+maghead.offp,maghead.sizp);
*/
rx = maghead.rx;
ry = maghead.ry;
lx = maghead.lx;
ly = maghead.ly;
screen_mode = maghead.screen;
image_mode = maghead.screen;
fread(pal,1,(image_mode&COL256)?768:48,fp); /* palette read */
return TRUE;
}
int mag_decode(FILE *fp,int mode,int x,int y)
{
/* flag a size */
xpixel = (maghead.screen&COL256)?(maghead.rx/4-maghead.lx/4+1)
:(maghead.rx/8-maghead.lx/8+1);
siza = (xpixel*(maghead.ry-maghead.ly+1)+7) / 8;
/* xpixel = 横方向のピクセル数の半分 */
if ((flga=(char *)malloc(siza))==NULL) {
printf("magl : can't allocate memory ( flag a )\n");
goto Exit;
}
if ((flgb=(char *)malloc(maghead.sizb))==NULL) {
printf("magl : can't allocate memory ( flag b )\n");
goto Exit;
}
if ((pix=(char *)malloc(maghead.sizp))==NULL) {
printf("magl : can't allocate memory ( pixcel )\n");
goto Exit;
}
if ((flg=(char *)malloc(siza*8))==NULL) {
printf("magl : can't allocate memory ( flag )\n");
goto Exit;
}
if(!(mode&VRAM)) {
vram=(char *)calloc(1,siza*32+(xpixel*8*32));
/* ↑モザイクのために8ライン余分に確保! */
if (vram==NULL) printf("magl : memory allocate error (vram)\n");
}
fseek(fp,headtop+maghead.offa,0); /* flag a read */
if (fread(flga,1,siza,fp)!=siza)
printf("magl : inproper size ( flag a )\n");
fseek(fp,headtop+maghead.offb,0); /* flag b read */
if (fread(flgb,1,maghead.sizb,fp)!=maghead.sizb)
printf("magl : inproper size ( flag b )\n");
fseek(fp,headtop+maghead.offp,0); /* pixcel read */
if (fread(pix,1,maghead.sizp,fp)!=maghead.sizp)
printf("magl : inproper size ( pixcel )\n");
if ((vram!=NULL)&&(!(mode&VRAM)))
Lineofs = (unsigned int)xpixel*8;
else if (mode&DOS)
Lineofs = (unsigned int)640;
else
Lineofs = (unsigned int)1024*((maghead.screen&COL256)?2:1);
Mofs[0] = -(int)(( 0+ 0*Lineofs)/2);
Mofs[1] = -(int)(( 4+ 0*Lineofs)/2);
Mofs[2] = -(int)(( 8+ 0*Lineofs)/2);
Mofs[3] = -(int)((16+ 0*Lineofs)/2);
Mofs[4] = -(int)(( 0+ 1*Lineofs)/2);
Mofs[5] = -(int)(( 4+ 1*Lineofs)/2);
Mofs[6] = -(int)(( 0+ 2*Lineofs)/2);
Mofs[7] = -(int)(( 4+ 2*Lineofs)/2);
Mofs[8] = -(int)(( 8+ 2*Lineofs)/2);
Mofs[9] = -(int)(( 0+ 4*Lineofs)/2);
Mofs[10] = -(int)(( 4+ 4*Lineofs)/2);
Mofs[11] = -(int)(( 8+ 4*Lineofs)/2);
Mofs[12] = -(int)(( 0+ 8*Lineofs)/2);
Mofs[13] = -(int)(( 4+ 8*Lineofs)/2);
Mofs[14] = -(int)(( 8+ 8*Lineofs)/2);
Mofs[15] = -(int)(( 0+16*Lineofs)/2);
Lineofs /= 2;
if ((vram!=NULL)&&(!(mode&VRAM))) { /* メインメモリに展開 */
/* printf("magl : pixel decode to main memory\n"); */
mag((char *)(&maghead),mode|(!vram),0,xpixel);
} else if (!(mode&DOS)) { /* 16/256色モード */
vram = NULL;
if ((maghead.rx-maghead.lx)>1023) {
printf("magl : picture is too wide \n");
goto Exit;
}
if ((maghead.ry-maghead.ly)>511) {
maghead.ly = 0;
maghead.ry = 511;
y = 0;
}
if ((maghead.rx+x)>1023||(maghead.ry+y)>511
||(maghead.lx+x)<0||(maghead.ly+y)<0) {
x = 0;
y = 0;
}
/* printf("magl : pixcel decode to vram (16/256)\n"); */
mag((char *)(&maghead),mode|VRAM
,(x+y*1024)/((maghead.screen&COL256)?1:2),xpixel);
/* printf("magl : pixcel decode end \n"); */
} else { /* DOS互換モード */
vram = NULL;
if (maghead.screen&COL256) {
printf("magl : irregal screen mode\n");
goto Exit;
}
if ((maghead.rx-maghead.lx)>639) {
printf("magl : picture is too wide \n");
goto Exit;
}
if ((maghead.ry-maghead.ly)>399) {
maghead.ly = 0;
maghead.ry = 399;
y = 0;
}
if ((maghead.rx+x)>639||(maghead.ry+y)>399
||(maghead.lx+x)<0||(maghead.ly+y)<0) {
x = 0;
y = 0;
}
/* printf("magl : pixcel decode to vram (MS-DOS)\n"); */
mag((char *)(&maghead),mode|VRAM,(x+y*640)/2,xpixel);
/* printf("magl : pixcel decode end\n"); */
}
/* flag_write(); */
free(flg);
free(pix);
free(flgb);
free(flga);
flg = NULL; pix = NULL; flgb = NULL; flga = NULL;
return TRUE;
Exit:
if (flg!=NULL)
free(flg);
if (pix!=NULL)
free(pix);
if (flgb!=NULL)
free(flgb);
if (flga!=NULL)
free(flga);
flg = NULL; pix = NULL; flgb = NULL; flga = NULL;
return FALSE;
}
int mki_get_head(FILE *fp)
{
int i;
unsigned char tmp;
headtop = 0;
fseek(fp,0,0);
if (fread((char *)&mkihead,1,sizeof(MKIHEADER),fp)<sizeof(MKIHEADER))
return FALSE;
if ((!stringcmp("MAKI01A",mkihead.id))&&(!stringcmp("MAKI01B",mkihead.id)))
return FALSE;
for(i=0;i<23;i++)
comment[i]=(mkihead.comment[i]<0x20)?' ':mkihead.comment[i];
comment[23]='\0';
/* モトローラ形式 -> インテル形式 */
tmp = mkihead.sizb.m.h ;
mkihead.sizb.m.h = mkihead.sizb.m.l ;
mkihead.sizb.m.l = tmp ;
tmp = mkihead.sizpa.m.h ;
mkihead.sizpa.m.h = mkihead.sizpa.m.l ;
mkihead.sizpa.m.l = tmp ;
tmp = mkihead.sizpb.m.h ;
mkihead.sizpb.m.h = mkihead.sizpb.m.l ;
mkihead.sizpb.m.l = tmp ;
sizp = mkihead.sizpa.s + mkihead.sizpb.s;
/*
printf(
"------------------------\n"
" Header Information \n"
"------------------------\n"
"header size : 48\n"
"palettesize : 48\n"
"flag a size : 1000\n"
"flag b size : %d\n"
"pixcel size : %d\n"
"------------------------\n"
,mkihead.sizb.s,sizp);
*/
lx = 0;
ly = 0;
rx = 639;
ry = 399;
screen_mode = 0;
image_mode = 0;
fread(pal,1,48,fp); /* palette read */
}
int mki_decode(FILE *fp,int mode,int x,int y)
{
/* flag a size : 1000 = 320*400 / (4*4) / 8 */
if ((flga=(char *)malloc(1000))==NULL) {
printf("magl : can't allocate memory ( flag a )\n");
goto Exit;
}
if ((flgb=(char *)malloc(mkihead.sizb.s))==NULL) {
printf("magl : can't allocate memory ( flag b )\n");
goto Exit;
}
if ((pix=(char *)malloc(sizp))==NULL) {
printf("magl : can't allocate memory ( pixcel )\n");
goto Exit;
}
/* flag size : 16000 = 320*400 / 8 */
if ((flg=(char *)malloc(16000))==NULL) {
printf("magl : can't allocate memory ( flag )\n");
goto Exit;
}
/* vram : 128000 = 640 * 400 / 2 */
if (!(mode&VRAM))
vram = (char *)calloc(1,128000+((rx/8-lx/8+1)*4*32));
fread(flga,1,1000,fp); /* flag a read */
fread(flgb,1,mkihead.sizb.s,fp); /* flag b read */
fread(pix,1,sizp,fp); /* pixcel read */
if ((vram!=NULL)&&(!(mode&VRAM))) { /* メインメモリに展開 */
/* printf("magl : mki decode to main memory\n"); */
mki((char *)(&mkihead),mode|(!VRAM),0);
} else if (!(mode&DOS)) { /* 1024*512/16色モード */
vram = NULL;
if ((x+639)>1023||(y+399)>511||x<0||y<0) {
x = 0;
y = 0;
}
mki((char *)(&mkihead),mode|VRAM,(x+y*1024)/2);
/* printf("magl : mki pixcel decode end \n"); */
} else { /* DOS互換モード */
vram = NULL;
mki((char *)(&mkihead),mode|VRAM,0);
/* printf("magl : mki pixcel decode end\n"); */
}
free(flg);
free(pix);
free(flgb);
free(flga);
flg = NULL; pix = NULL; flgb = NULL; flga = NULL;
return TRUE;
Exit:
if (flg!=NULL)
free(flg);
if (pix!=NULL)
free(pix);
if (flgb!=NULL)
free(flgb);
if (flga!=NULL)
free(flga);
flg = NULL; pix = NULL; flgb = NULL; flga = NULL;
return FALSE;
}
int display(int slx,int sly,int ssx,int ssy,int dx,int dy)
{
if (screen_mode&DOS)
move(ssx/2,ssy,(int)vram+(lx%8+slx+sly*(rx/8-lx/8+1)*8)/2
,(rx/8-lx/8+1)*8/2,0x0104,(dx+dy*640)/2,320);
else if (screen_mode&COL256)
move(ssx,ssy,(int)vram+(lx%4+slx+sly*(rx/4-lx/4+1)*4),(rx/4-lx/4+1)*4
,0x010c,(dx+dy*1024),1024);
else
move(ssx/2,ssy,(int)vram+(lx%8+slx+sly*(rx/8-lx/8+1)*8)/2
,(rx/8-lx/8+1)*8/2,0x0104,(dx+dy*1024)/2,512);
return TRUE;
}
int set_palette(void)
{
unsigned char *p;
int i,r,g,b;
if (image_mode&COL256)
for (i=0,p=(unsigned char *)pal;i<256;i++) {
g = (int)*p++;
r = (int)*p++;
b = (int)*p++;
outpb(PALNO,i);
outpb(PALB,b);
outpb(PALR,r);
outpb(PALG,g);
}
else
for (i=0,p=(unsigned char *)pal;i<16;i++) {
g = ((int)*p++)&0xf0;
r = ((int)*p++)&0xf0;
b = ((int)*p++)&0xf0;
outpb(PALNO,i);
outpb(PALB,b);
outpb(PALR,r);
outpb(PALG,g);
}
return TRUE ;
}